from datetime import datetime
from typing import Optional
from pydantic import BaseModel
from bson import ObjectId

class PyObjectId(ObjectId):
    @classmethod
    def __get_validators__(cls):
        yield cls.validate

    @classmethod
    def validate(cls, v):
        if not ObjectId.is_valid(v):
            raise ValueError("Invalid objectid")
        return ObjectId(v)

    @classmethod
    def __modify_schema__(cls, field_schema):
        field_schema.update(type="string")

class AICharacterBase(BaseModel):
    name: str
    avatar: Optional[str] = None
    personality: Optional[str] = None
    background: Optional[str] = None
    is_public: bool = False

class AICharacterCreate(AICharacterBase):
    pass

class AICharacterUpdate(BaseModel):
    name: Optional[str] = None
    avatar: Optional[str] = None
    personality: Optional[str] = None
    background: Optional[str] = None
    is_public: Optional[bool] = None

class AICharacterInDBBase(AICharacterBase):
    id: PyObjectId
    creator_id: PyObjectId
    created_at: datetime
    updated_at: datetime
    interaction_count: int = 0

    class Config:
        arbitrary_types_allowed = True
        json_encoders = {ObjectId: str}

class AICharacter(AICharacterInDBBase):
    pass

class AICharacterInDB(AICharacterInDBBase):
    pass